home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Ham Radio 2000
/
Ham Radio 2000.iso
/
ham2000
/
bbs
/
diebox19
/
read.c
< prev
next >
Wrap
Text File
|
1992-10-14
|
21KB
|
946 lines
/* read.c */
#define VERSION "1.2"
/* DL6HAZ Jul. 1992
*
*/
/*--------------------------------------------------------------------
DL1BDY 13.10.92 : Anpassung an DIEBOX 1.9
- Pfade für B und C jetzt unterhalb des BACKUP-DIR
- Einführung einer weiteren Env-Var "BACK_DIR"
- Beim EXPORT aus B oder C wird in das EXPORT-File
jeweils der originale Filename eingetragen. Somit
ist ein einfacherer Rücktransfer in INFO-Boards
möglich.
-----------------------------------------------------------------------
*/
#include <stdio.h>
#include <time.h>
#include <fcntl.h>
#include <ctype.h>
#include <string.h>
#include <io.h>
/* #define KEYB */ /* Read-Program stdout/stdin, man. Eing. von Binfilename*/
/*#define LIST */ /* List-Program stdout nicht mit KEYB o. READ verw. */
#define READ /* Export- oder ReadProgram abhaengig von KEYB */
/*#define DEBUG*/
#ifdef LIST
#undef KEYB
#undef READ
#endif
#define IDXLENGTH 115
#define BoxNullTime 536454000L /*01.01.87*/
char *GetMsg();
char *lcase();
char *upcase();
char *getenv();
unsigned long absLDat();
unsigned long absDat();
extern int atoi();
extern long atol();
extern long timezone = 0l;
extern int daylight = 0;
extern int _fmode;
extern unsigned _stklen;
char MultiBuff[10000];
unsigned crctab[256];
int FileCount = 0;
long glob_bytecount =0;
int err_count = 0;
main(argc, argv)
int argc;
char *argv[];
{
int von, bis;
int priv;
int plus;
time_t LastLogin;
unsigned char searchstr[IDXLENGTH+1];
char filename[IDXLENGTH+1];
char Language[5];
char *ptr;
int i=1;
extern int optind;
extern char *optarg;
/* Defaultwerte einstellen */
von = 0;
bis = 0;
searchstr[0] = '*'; /* any string matches */
searchstr[1] = '\0';
*filename = '\0';
time(&LastLogin);
sprintf(Language, "%s", getenv("DEFAULT_LANG"));
priv = 1;
plus = 1; /* Ausgabe mit vollen Header */
#ifdef KEYB
plus = 0; /* Ausgabe mit verkuerzten Header */
#endif
/* Program Header ausgeben */
#ifndef KEYB
#ifdef READ
fprintf(stdout, " EXPMSG\n");
#endif
#endif
#ifdef LIST
fprintf(stdout, " LIST\n");
#endif
#ifdef KEYB
#ifdef READ
fprintf(stdout, " READ\n");
#endif
#endif
fprintf(stdout, " Version %s\n", VERSION);
fprintf(stdout, " %s\n\n", __DATE__);
#ifndef KEYB
#ifdef READ
fprintf(stdout, " Export-Utilitie for THEBOX 1.9\n");
fprintf(stdout, " for Text- or BinFiles!\n");
fprintf(stdout, " For HELP call EXPMSG without any Arguments!\n");
#endif
#endif
/* filename bestimmen */
if(argv[i] != NULL){
sprintf(filename, "%s", argv[i]);
#ifdef DEBUG
fprintf(stderr, "\nFilename: %s\n", filename);
#endif
}
else{
help();
exit(1);
}
memset(MultiBuff, '\0', sizeof(MultiBuff));
for(i = 2; argv[i] != NULL; i++)
strcat(MultiBuff, argv[i]);
#ifdef DEBUG
fprintf(stderr, "Commandline: %s\n", MultiBuff);
#endif
if((ptr = strchr(MultiBuff, '!')) != NULL){
*ptr = '\0';
sscanf(ptr+1, "%s", searchstr);
upcase(searchstr);
von = 1;
bis = 9999;
}
if((ptr = strchr(MultiBuff, '-')) != NULL){
*ptr = '\040';
if(*(ptr+1) != '\0'){
sscanf(ptr+1, "%d", &bis);
von = 1;
}
if(&MultiBuff[0] != ptr){
sscanf(MultiBuff, "%d", &von);
if(bis == 0) bis = 9999;
}
}
else
if(isdigit(MultiBuff[0])){
sscanf(MultiBuff, "%d", &von);
bis = von;
}
#ifdef DEBUG
fprintf(stderr, "\nvon %d bis %d searchstr %s\n", von, bis, searchstr);
#endif
#ifndef KEYB
#ifdef READ
fprintf(stdout, "\n\nExport: %s %d - %d !%s\n", filename,
von,
bis,
searchstr);
#endif
#endif
init_crctab();
if((*filename == '\0') || ((strlen(filename)<2)&&(!priv))){
printf("%s\n", GetMsg(8, Language));
exit(1);
}
else
ReadRoutine(filename, von, bis, searchstr, plus , Language, LastLogin);
#ifdef READ
#ifndef KEYB
fprintf(stdout,
"\n\nExport OK!\nMsg: %d Bytes: %ld Errors: %d\n\n",
FileCount,
glob_bytecount,
err_count);
#endif
#endif
}
ReadRoutine(Filename, Von, Bis, Betreff, PlusFound, Lang, LastLogin)
char *Filename;
int Von;
int Bis;
unsigned char *Betreff;
int PlusFound;
char *Lang;
time_t LastLogin;
{
unsigned int Last,i;
char DName[IDXLENGTH+1];
int found;
int pnmatch();
char ChanStr[80];
char ReadDir[80];
long LastPos;
time_t ProtTime;
struct tm *utc;
FILE *Prot_fp;
FILE *List_fp;
FILE *Read_fp;
/*------------ ergänzt von DL1BDY, 13.10.92 ------------------------ */
if ((strncmp(Filename, "B",1) == 0) || (strncmp(Filename, "b",1) == 0) ||
(strncmp(Filename, "C",1) == 0) || (strncmp(Filename, "c",1) == 0))
{
sprintf(ReadDir, "%s%s", getenv("BACK_DIR"), Filename);
/* sprintf(ReadDir, "D:\\BACKUP\\%s\\", Filename); */
}
/* -------------------- bis hier --------------------- */
else
{
if(isCall(Filename))
sprintf(ReadDir, "%s%s", getenv("USR_DIR"), Filename);
else
sprintf(ReadDir, "%s%s", getenv("INFO_DIR"), Filename);
}
sprintf(ChanStr, "%s\\protfile.dat", ReadDir);
if((Prot_fp = fopen(ChanStr, "r")) != NULL){
fseek(Prot_fp, 0L, 2);
LastPos = ftell(Prot_fp);
}
else{
fprintf(stdout, "%s %s\n", GetMsg(10, Lang), Filename);
exit(1);
}
Last = (int)(LastPos / (long)(IDXLENGTH));
if (Bis > Last) Bis = Last;
if((Von == 0) && (Bis == 0)){
if (Last > 0){
found = 0;
fseek(Prot_fp,0l, 0);
for(i=1;(i<=Last) && (! found);i++){
fgets(DName, IDXLENGTH+1, Prot_fp);
DName[27] = '\0';
if(strchr((DName+13), '.') != NULL )
ProtTime = absLDat(DName+13); /* Umrechnug Boxtime nach sec */
else
sscanf(DName+13, "%X", &ProtTime);
if(ProtTime > LastLogin) found = 1;
}
if (found){
Von = i-1;
Bis = Last;
}
else{
fprintf(stdout, "%s\n\n", GetMsg(58, Lang));
if(isCall(Filename))
printf("Userfile %s:\n", upcase(Filename));
else
printf("Infofile %s:\n", upcase(Filename));
fprintf(stdout, "%s\n\n", GetMsg(5, Lang));
utc = gmtime(&ProtTime);
printf("%4d %6.6s %02d.%02d.%02d %02d:%02d %6.6s %40.40s\n",
Last,
DName+6,
utc->tm_mday,
utc->tm_mon+1,
utc->tm_year,
utc->tm_hour,
utc->tm_min,
DName+28,
DName+35);
exit(0);
}
}
} /* if von = 0 && bis = 0 */
#ifdef DEBUG
fprintf(stderr, "\nvon %d bis %d\n", Von, Bis);
#endif
if (Von <= Bis)
{
#ifdef LIST
List_fp = stdout;
#endif
#ifdef READ
#ifndef KEYB
mkdir(Filename);
sprintf(ChanStr, "%s\\list.exp", Filename);
List_fp = fopen(ChanStr, "w");
#endif
#endif
#ifndef KEYB
if(isCall(Filename))
fprintf(List_fp, "Userfile %s:\n", upcase(Filename));
else
fprintf(List_fp, "Infofile %s:\n", upcase(Filename));
fprintf(List_fp, "%s\n\n", GetMsg(5, Lang));
#endif
for(i = Von; i <= Bis; i++){
LastPos = (long)(IDXLENGTH) * (long)(i-1);
fseek(Prot_fp, LastPos, 0);
if(fgets(DName, IDXLENGTH, Prot_fp)== NULL) break;
if (pnmatch(DName,Betreff, 1) == 1){
#ifndef KEYB
DName[27] = '\0';
if(strchr((DName+13), '.') != NULL )
ProtTime = absLDat(DName+13); /* Umrechnug Boxtime nach sec */
utc = gmtime(&ProtTime);
fprintf(List_fp,
"%4d %6.6s %02d.%02d.%02d %02d:%02d %6.6s %40.40s\n",
i,
DName+6,
utc->tm_mday,
utc->tm_mon+1,
utc->tm_year,
utc->tm_hour,
utc->tm_min,
DName+28,
DName+35);
#endif
#ifdef READ
FileCount++;
DName[6]='\0';
sprintf(ChanStr, "%s\\%s", ReadDir, DName);
#ifdef DEBUG
fprintf(stderr, "%s\n", ChanStr);
#endif
if((Read_fp= fopen(ChanStr, "rb")) != NULL){
setvbuf(Read_fp, NULL, _IOFBF, 10240);
ReadMsg(Read_fp, PlusFound, Lang, Filename, i);
glob_bytecount += ftell(Read_fp);
fclose(Read_fp);
}
else{
printf("%s\n", GetMsg(8, Lang));
err_count++;
}
#endif
}
} /* for i... */
}
fclose(Prot_fp);
#ifdef READ
#ifndef KEYB
fclose(List_fp);
#endif
#endif
}
int isCall(Call)
char *Call;
{
int ok;
int length;
int count;
char *uc;
length = strlen(Call);
/*printf("Laenge ");*/
if((length > 2) && (length < 7))
ok = 1;
else ok = 0;
if(Call[0] > 0x7F) ok = 0;
if(ok == 1)
{
/*printf("Zahlen 2+3 ");*/
if((isdigit(*(Call +1))) || (isdigit(*(Call +2)))) ok = 1;
else ok = 0;
}
if(ok == 1)
{
/*printf("Letztes keine Zahl ");*/
if(!isdigit(*(Call + length -1))) ok = 1;
else ok = 0;
}
if(ok == 1)
{
/*printf("Suffix-Length ");*/
uc = Call + length ;
count = 0;
do
{
uc -= 1;
count++;
}
while((count < 5) && (isdigit(*uc) == 0));
if(count < 5) ok = 1;
else ok = 0;
}
if(ok == 1)
{
/*printf("Zahlen 1+2 ");*/
uc = Call;
if((isdigit(*uc++))&&(isdigit(*uc))) ok = 0;
else ok = 1;
}
return(ok);
}
int Schaltjahr(Jahr)
unsigned int Jahr;
{
if(Jahr % 4 == 0 && Jahr % 100 != 0 || Jahr % 400 == 0) return(1);
return(0);
}
unsigned int absTime(CharPtr)
unsigned char *CharPtr;
{
char StrStunde[3];
char StrMinute[3];
int Stunde,Minute;
sprintf(StrStunde,"%2.2s",CharPtr+ 9);
sprintf(StrMinute,"%2.2s",CharPtr+12);
sscanf(StrStunde,"%d",&Stunde);
sscanf(StrMinute,"%d",&Minute);
return((Stunde*60) + Minute);
}
unsigned long absDat(CharPtr)
unsigned char *CharPtr;
{
char Tag[3];
char Monat[3];
char Jahr[3];
unsigned long NumTag;
unsigned long NumJahr;
unsigned long NumMonat;
unsigned long result;
unsigned int Mon;
int i;
sprintf(Tag,"%2.2s",CharPtr);
sprintf(Monat,"%2.2s",CharPtr + 3);
sprintf(Jahr,"%2.2s",CharPtr + 6);
sscanf(Tag,"%ld",&NumTag);
sscanf(Monat,"%ld",&NumMonat);
sscanf(Jahr,"%ld",&NumJahr);
NumJahr += 1900;
for (i=1987,result=0L;i<NumJahr;i++)
{
if(Schaltjahr(i)) result += 366;
else result += 365;
}
for(i=1;i<NumMonat;i++)
{
switch(i)
{
case 1:
case 3:
case 5:
case 7:
case 8:
case 10:
case 12: Mon = 31;
break;
case 2: if(Schaltjahr((unsigned int)NumJahr)) Mon = 29; else Mon = 28;
break;
default: Mon = 30;
break;
}
result += Mon;
}
result += NumTag;
return(result - 1);
}
unsigned long absLDat(String)
char *String;
{
unsigned long retval;
retval = absDat(String);/* Tage */
retval *= 1440; /* Minuten */
/* Stunden noch dazu */
retval += (absTime(String));
retval = retval*60+BoxNullTime+3600;
return(retval);
}
/*
* Convert a string to upper case.
*/
char *
upcase(s)
char *s;
{
register char *p, c;
for(p = s; c = *p; p++)
if((c >= 'a') && (c <= 'z'))
*p = c + 'A' - 'a';
return(s);
}
/*
* Convert a string to lower case.
*/
char *
lcase(s)
char *s;
{
register char *p, c;
for(p = s; c = *p; p++)
if((c >= 'A') && (c <= 'Z'))
*p = c + 'a' - 'A';
return(s);
}
ReadMsg(Read_fp, PlusFound, Lang, ExName, count)
FILE *Read_fp;
int PlusFound;
char *Lang;
char *ExName;
int count;
{
int i = 0;
static int status = 0;
char HeadLine[100];
char Titel[100];
char ChanStr[100];
char BoxSName[10];
char BullID[20];
char ZielMB[20];
char *ptr1;
char *ptr2;
FILE *ex_fp;
fseek(Read_fp, 3l, 0);
fgets(HeadLine, 100, Read_fp);
sscanf(HeadLine, "%8s", BoxSName);
#ifdef DEBUG
fprintf(stderr, "BoxSName %s ExName %s\n", BoxSName, ExName);
#endif
sscanf(HeadLine+strlen(BoxSName), "%12s", ZielMB);
if((ptr1 = strchr(ZielMB, '.')) != NULL) *ptr1 = '\0';
if(strncmp(BoxSName, ExName, 8) != 0) *ZielMB = '\0';
fgets(Titel, 100, Read_fp);
if(PlusFound){
sprintf(ChanStr, "%s\\export.txt", ExName);
if(status == 0){
ex_fp = fopen(ChanStr, "wb");
status++;
}
else{
if((ex_fp = fopen(ChanStr, "ab")) == NULL){
perror("ReadMsg(): ex_fp");
exit(1);
}
fseek(ex_fp, 0l, 2);
}
/* -------DL1BDY 13.10.92
Bei Export aus "B" oder "C" wird der originale Rubrikname gesetzt.
Grund: Mails aus "B" oder "C" bekommt man nur wieder in die CHECK-
Liste, wenn man exportiert und anschliessend in die Original-Rubrik
importiert.
--------------------------------------------------------------- */
if ( (strncmp(ExName,"B",1) == 0) || (strncmp(ExName, "C",1) == 0 ))
ExName = BoxSName ;
fprintf(ex_fp, "S %s %s < %.6s",
ExName,
ZielMB,
HeadLine+20);
fgets(ChanStr, 80, Read_fp);
if(strncmp(ChanStr, "*** Bulletin-ID:",16) == 0){
sscanf(ChanStr+16, "%13s", BullID);
fprintf(ex_fp, " $%s", BullID);
}
fgets(ChanStr, 80, Read_fp); /* Rcv from */
if(isdigit(HeadLine[43]))
fprintf(ex_fp, " #%.3s", HeadLine+43);
sprintf(MultiBuff,
"R:%-2.2s%-2.2s%-2.2s/%-2.2s%-2.2sz @%-6.6s [%s]",
HeadLine+33,
HeadLine+30,
HeadLine+27,
HeadLine+36,
HeadLine+39,
getenv("OWNBBS"),
GetMsg(14, Lang)
);
fprintf(ex_fp, "\r\n%s", Titel);
fprintf(ex_fp, "%s", MultiBuff);
get_text(Read_fp, ex_fp, ExName, count);
fclose(ex_fp);
}
else{
fputs(HeadLine, stdout);
fputs(Titel, stdout);
fgets(ChanStr, 80, Read_fp);
fputs(ChanStr, stdout);
fgets(ChanStr, 80, Read_fp);
fgets(ChanStr, 80, Read_fp);
fgets(MultiBuff, 90, Read_fp);
if(strncmp(MultiBuff, "R:", 2) == 0){
fprintf(stdout, "\n");
while(strncmp(MultiBuff, "R:", 2) == 0){
ptr1 = strchr(MultiBuff, '@');
while(!isalnum(*ptr1++));
ptr1--;
ptr2 = ptr1;
while(isalnum(*ptr2++));
*(ptr2-1) = '\0';
sprintf(ChanStr, "%s%-12.12s %-6.6s", i?", ":"\0",
MultiBuff+2,
ptr1);
fputs(ChanStr, stdout);
i++;
if( i == 3){
i = 0;
fputc('\n', stdout);
}
fgets(MultiBuff, 100, Read_fp);
}
fprintf(stdout, "\n");
}
else
fputc('\n', stdout);
fputs(MultiBuff, stdout);
get_text(Read_fp, stdout, ExName, count);
} /* else */
}
char *GetMsg(MsgNo, Lang)
int MsgNo;
char *Lang;
{
int i;
char Filename[80];
static char msg[255];
FILE *stream;
sprintf(Filename, "%s/msg%s.box", getenv("MBSYS_DIR"), Lang);
stream = fopen(Filename, "r");
if(stream != NULL){
for (i = 1; (fgets(msg, 255, stream) != NULL)&&(i != MsgNo); i++);
fclose(stream);
*(msg+strlen(msg)-1) = '\0';
return (&msg[0]);
}
return NULL;
}
help()
{
fprintf(stdout, "\n\nSyntax: \n\n");
fprintf(stdout, "<Call/Rubrik> <von/bis/!searchstr>\n\n");
#ifndef KEYB
#ifdef READ
fprintf(stdout, "Die exportierten Nachrichten werden in Directory abglegt\n");
fprintf(stdout, "der dem Call bzw. der Rubrik entspricht.\n\n");
fprintf(stdout, "In diesem Directory befinden sich weiterhin:\n\n");
fprintf(stdout, "EXPORT.TXT - der Text.\n");
fprintf(stdout, "LIST.EXP - wie der List-Befehl.\n");
fprintf(stdout, "#.bin - die evt. Bin-Files, # entspricht der Nummer,\n");
fprintf(stdout, " der entsprechend, Nachricht.\n\n");
#endif
#endif
exit(0);
}
/* heisst nur pnmatch() weil es in einer Coh-Version eine derartige Fkt. */
/* gibt. Hat ansonsten damit nichts zutun! */
pnmatch(DName, Searchstr)
char *DName;
char *Searchstr;
{
char Protzeile[IDXLENGTH+1];
sprintf(Protzeile, "%s", DName);
upcase(Protzeile);
if(*Searchstr == '*')
return 1;
if(strstr(Protzeile, Searchstr) == NULL)
return 0;
else
return 1;
}
get_text(Read_fp, exp_fp, ExName, count)
FILE *Read_fp;
FILE *exp_fp;
char *ExName;
int count;
{
int i;
int BinFound = 0;
int BinFlag = 0;
unsigned BoxCRC = 0;
unsigned crc = 0;
unsigned get_bin();
long ReadPos;
long BinBytes = 0;
char StartBin[] = "\n#BIN#";
char BinBuff[100];
char BinFilename[80];
char *ptr;
FILE *bin_fp;
memset(BinBuff, '\0', sizeof(BinBuff));
for(; (BinBuff[BinFound] = fgetc(Read_fp)) != -1; ){
if(BinBuff[BinFound] == '\n' || BinFound > 0){
if(BinBuff[BinFound] == StartBin[BinFound]){
BinFound++;
BinBuff[BinFound] = '\0';
}
else
BinFound = 0;
}
if(BinFound == 6){
ReadPos = ftell(Read_fp);
#ifdef DEBUG
fprintf(stderr, "\n*** Bin found ***\n");
fprintf(stderr, "%ld\n", ReadPos);
#endif
for( ;
((BinBuff[BinFound]=fgetc(Read_fp)) != '\r') && (BinFound < 99);
BinFound++)
if(BinBuff[BinFound] == '#') BinBuff[BinFound] = '\040';
*(BinBuff+BinFound+1) = '\0';
if(BinBuff[BinFound] == '\r'){
if((ptr=strchr(BinBuff+6, '|')) != NULL)
BoxCRC = atoi(ptr+1);
BinBytes = atol(BinBuff+6);
}
if(BinBytes != 0 && BoxCRC != 0){ /* Success ist BIN */
BinFlag = 1;
#ifdef KEYB
fprintf(stderr,
"Please enter filename for binary export: ");
fgets(BinFilename, 70, stdin);
if(*BinFilename == '\n')
break;
else
*(BinFilename+strlen(BinFilename)-1) = '\0';
#else
sprintf(BinFilename, "%s\\%d.bin", ExName, count);
fprintf(exp_fp, "\n#BIN##%d.bin\r\n", count);
#endif
fprintf(stderr, "\n#BIN#%ld#|%u#%s\n", BinBytes,
BoxCRC,
BinFilename);
if((bin_fp = fopen(BinFilename, "wb")) == NULL){
perror("Opening Binfilename");
err_count++;
break;
}
crc = get_bin(BinBytes, Read_fp, bin_fp);
fprintf(stderr, "\n#OK#\n");
fprintf(stderr, "Export-CRC: %u/%u\n\n", BoxCRC, crc);
if(BoxCRC != crc){
err_count++;
}
fclose(bin_fp);
break;
}
else{ /* Failure war doch kein BIN */
BinFound = 0;
BinBuff[5] = '\0';
fseek(Read_fp, ReadPos, 0);
}
}
if(BinFound == 0){
for(i =0; BinBuff[i] != '\0'; i++)
fputc(BinBuff[i], exp_fp);
memset(BinBuff, '\0', sizeof(BinBuff));
}
}
if(BinFlag == 0){
for(i =0; BinBuff[i] > 0; i++){
fputc(BinBuff[i], exp_fp);
}
fprintf(exp_fp,"***END\r\n");
}
}
/*
* CCITT Polynom x^16 + x^12 + x^5 + 1
*
* hier im Gegensatz zu CCITT, (A)X.25:
* - Datenbyte MSB zuerst
* - CRC-Start mit 0
* - keine Multiplikation Nachricht mit x^16
* (CRC wird bei Empfang nicht ueber CRC-Bytes berechnet)
* - kein Invertieren des CRC
*
* wird z.B. benutzt von: UoSat DCE, SEVEN
*/
/*unsigned crctab[256];
unsigned crc;
unsigned byte; */ /* Datenbyte, high Byte = 0 ! */
/*
* entweder beim Programmstart einmal aufrufen,
* oder die 512 Byte Tabelle einmal ausrechnen lassen und dann als
* initialisierte Tabelle ins Programm uebernehmen
*/
init_crctab()
{
unsigned n;
unsigned m;
unsigned r;
unsigned mask;
static unsigned bitrmdrs[] = { 0x9188,0x48C4,0x2462,0x1231,
0x8108,0x4084,0x2042,0x1021 };
for (n = 0; n < 256; ++n)
{
for (mask = 0x0080, r = 0, m = 0; m < 8; ++m, mask >>= 1)
if (n & mask) r = bitrmdrs[m] ^ r;
/*
* "if (n & mask) r ^= bitrmdrs[m];" ist kuerzer, aber Turbo C fuer
* den Atari ST, Version 1.0, uebersetzt das falsch
*/
crctab[n] = r;
}
}
/*
* byteweiser Algorithmus, C, portabel
*/
/*
void do_crc(void)
{
crc = crctab[crc >> 8] ^ (crc << 8 | byte);
}
*/
unsigned get_bin(Bytecount, Read_fp, bin_fp)
long Bytecount;
FILE *Read_fp;
FILE *bin_fp;
{
unsigned crc = 0;
unsigned byte;
long i;
for(i = 0; i < Bytecount && (byte = fgetc(Read_fp)) != -1; i++){
crc = crctab[crc >> 8] ^ (crc << 8 | byte);
fputc(byte, bin_fp);
}
return crc;
}